package com.two.screen.water.balance.ui

import android.annotation.SuppressLint
import android.app.Activity
import android.app.Application
import android.content.Context
import android.content.pm.ApplicationInfo
import android.database.sqlite.SQLiteDatabase
import androidx.multidex.MultiDex
import cn.jpush.android.api.JPushInterface
import com.alibaba.android.arouter.launcher.ARouter
import com.danikula.videocache.HttpProxyCacheServer
import com.lzy.okgo.OkGo
import com.lzy.okgo.https.HttpsUtils
import com.two.screen.water.balance.bean.database.DaoMaster
import com.two.screen.water.balance.bean.database.DaoSession
import com.two.screen.water.balance.bean.database.MySqlLiteOpenHelper
import com.two.screen.water.balance.listener.MyActivityLifecycleCallbacks
import com.two.screen.water.balance.net.MyHttpLoggingInterceptor
import com.two.screen.water.balance.ui.service.AppService
import com.two.screen.water.balance.utils.CommUtils
import okhttp3.OkHttpClient
import org.greenrobot.greendao.query.QueryBuilder
import java.security.SecureRandom
import java.security.cert.X509Certificate
import java.util.concurrent.TimeUnit
import java.util.logging.Level
import javax.net.ssl.HttpsURLConnection
import javax.net.ssl.SSLContext
import javax.net.ssl.TrustManager
import javax.net.ssl.X509TrustManager


/**
 * 创建者     Noel
 * 创建时间   2017/12/20 11:21
 */
class App : Application() {

    init {
    }

    override fun onCreate() {
        super.onCreate()
        registerActivityLifecycleCallbacks(object : MyActivityLifecycleCallbacks() {
            override fun onActivityResumed(activity: Activity) {
                AppService.mCurrentRunActivity = activity.packageName.plus(".").plus(activity.localClassName)
            }
        })
        context = this
        isDebug = isApkDebug(this)

        MultiDex.install(this)
        if (!isDebug) {
            // CrashReport.initCrashReport(applicationContext, "c2d304eecf", true)
        }
        //LogToFileUtils.init(this);
        initARouter()
        initGreenDao()
        initOkGo()
        //初始化屏幕的宽高，密度
        var dm = context!!.resources.displayMetrics
        screenWidth = dm.widthPixels
        screenHeight = dm.heightPixels
        density = dm.density
        d("App.density:$density")
        initAppService(this)
        JPushInterface.setDebugMode(isDebug);
        JPushInterface.init(this);
    }

    private fun initAppService(context: Context) {
        try {
            AppService.startAppService(context)
            //startService(Intent(this, LocalService::class.java))
        } catch (e: Exception) {
            d("initAppService->error:$e")
        }
    }

    private fun initARouter() {
        //是否进行ARouter调试(可以通过AppConfig.isDebug=true/false来判断日志的是否开启)
        if (isDebug) {
            //下面两句话必须放到init前面,否则配置无效
            ARouter.openLog();  //打印ARouter日志
            ARouter.openDebug();  //开启ARouter的调试模式(如果在InstantRun模式下运行,必须开启调试模式,线上版本需要关闭，否则有安全风险),
        }
        //官方建议在Application里面进行初始化(使用该注解路径至少两级)
        ARouter.init(this);
    }

    private fun initOkGo() {
        val builder = OkHttpClient.Builder()
        if (isDebug) {
            val loggingInterceptor = MyHttpLoggingInterceptor("OkGo")
            loggingInterceptor.setPrintLevel(MyHttpLoggingInterceptor.Level.BODY)        //log打印级别，决定了log显示的详细程度
            loggingInterceptor.setColorLevel(Level.INFO)                               //log颜色级别，决定了log在控制台显示的颜色
            builder.addInterceptor(loggingInterceptor)                                //添加OkGo默认debug日志
        }
        //方法一：信任所有证书,不安全有风险
        val sslParams1 = HttpsUtils.getSslSocketFactory()
        builder.sslSocketFactory(sslParams1.sSLSocketFactory, sslParams1.trustManager)
        //超时时间设置，默认60秒
        builder.readTimeout(60000L, TimeUnit.MILLISECONDS)     //全局的读取超时时间
        builder.writeTimeout(60000L, TimeUnit.MILLISECONDS)     //全局的写入超时时间
        builder.connectTimeout(60000L, TimeUnit.MILLISECONDS)  //全局的连接超时时间
        // 其他统一的配置
        // 详细说明看GitHub文档：https://github.com/jeasonlzy/
        OkGo.getInstance()
            .init(this)                           //必须调用初始化
            .setOkHttpClient(builder.build())               //建议设置OkHttpClient，不设置会使用默认的
            .retryCount = 0                                 //全局统一超时重连次数，默认为三次，那么最差的情况会请求4次(一次原始请求，三次重连请求)，不需要可以设置为0
        //.setCacheMode(CacheMode.NO_CACHE)               //全局统一缓存模式，默认不使用缓存，可以不传
        // .setCacheTime(CacheEntity.CACHE_NEVER_EXPIRE)   //全局统一缓存时间，默认永不过期，可以不传
    }

    companion object {

        @SuppressLint("StaticFieldLeak")
        var context: Context? = null
        var flag = -1 //用来标志 是否 被系统干掉了然后重启app

        //var updateTimes = 0 //更新次数
        fun instance() = context!!

        var isDebug: Boolean = false
        var screenWidth: Int = 0
        var screenHeight: Int = 0
        var density: Float = 0f
        var mDaoSession: DaoSession? = null
        var mSQLiteDatabase: SQLiteDatabase? = null
        var mDaoMaster: DaoMaster? = null
        @SuppressLint("StaticFieldLeak") var mHelper: MySqlLiteOpenHelper? = null

        val mDbName = "Balance16inch.db"
        val mDbDir = "db"

        /**
         * 标记当前串口状态(true:打开,false:关闭)
         */
        var isFlagSerial = false

        //判断是是否debug模式
        fun isApkDebug(context: Context): Boolean {
            return try {
                val info = context.applicationInfo
                info.flags and ApplicationInfo.FLAG_DEBUGGABLE != 0
            } catch (e: Exception) {
                false
            }/*true*/
        }

        fun handleSSLHandshake() {
            try {
                val trustAllCerts: Array<TrustManager> = arrayOf<TrustManager>(object : X509TrustManager {
                    override fun checkClientTrusted(chain: Array<out X509Certificate>?, authType: String?) {
                    }

                    override fun checkServerTrusted(chain: Array<out X509Certificate>?, authType: String?) {
                    }

                    override fun getAcceptedIssuers(): Array<X509Certificate?>? = arrayOfNulls(0)

                })
                val sc: SSLContext = SSLContext.getInstance("TLS")
                // trustAllCerts信任所有的证书
                sc.init(null, trustAllCerts, SecureRandom())
                HttpsURLConnection.setDefaultSSLSocketFactory(sc.socketFactory)
                HttpsURLConnection.setDefaultHostnameVerifier { hostname, session -> true }
            } catch (ignored: java.lang.Exception) {
            }
        }

        fun getProxy(context: Context): HttpProxyCacheServer? {
            val app: App = context.applicationContext as App
            return if (app.proxy == null) app.newProxy().also { app.proxy = it } else app.proxy
        }

    }


    private fun initGreenDao() {
        QueryBuilder.LOG_SQL = isDebug;
        QueryBuilder.LOG_VALUES = isDebug;
        //获取可写数据库
        mHelper = MySqlLiteOpenHelper(this, mDbName, null)//建库

        //获取数据库对象
        mSQLiteDatabase = mHelper?.writableDatabase
        mDaoMaster = DaoMaster(mSQLiteDatabase)
        mDaoSession = mDaoMaster?.newSession()
    }

    private var proxy: HttpProxyCacheServer? = null
    private fun newProxy(): HttpProxyCacheServer? {
        return HttpProxyCacheServer.Builder(this)
            .maxCacheSize(1024 * 1024 * 1024)       // 2 Gb for cache
            .build();

    }

    private fun d(msg: String) {
        CommUtils.println("App->", msg)
    }

}